package com.wuzheng.wisgo.sanitation.cloud.service.plan.impl;

import com.baomidou.mybatisplus.mapper.EntityWrapper;
import com.baomidou.mybatisplus.mapper.Wrapper;
import com.baomidou.mybatisplus.plugins.Page;
import com.wuzheng.wisgo.sanitation.cloud.constant.Constants;
import com.wuzheng.wisgo.sanitation.cloud.constant.ErrorConst;
import com.wuzheng.wisgo.sanitation.cloud.enums.InfixDataEnum;
import com.wuzheng.wisgo.sanitation.cloud.model.plan.param.JobPlanDetailParam;
import com.wuzheng.wisgo.sanitation.cloud.model.plan.param.JobPlanSaveParam;
import com.wuzheng.wisgo.sanitation.cloud.model.plan.param.JobPlanListParam;
import com.wuzheng.wisgo.sanitation.cloud.model.plan.pojo.JobPlanDTO;
import com.wuzheng.wisgo.sanitation.cloud.model.plan.pojo.JobPlanDetailDTO;
import com.wuzheng.wisgo.sanitation.cloud.model.plan.pojo.JobPlanDetailRouteDTO;
import com.wuzheng.wisgo.sanitation.cloud.repository.entity.person.User;
import com.wuzheng.wisgo.sanitation.cloud.repository.entity.plan.*;
import com.wuzheng.wisgo.sanitation.cloud.repository.mapper.plan.JobPlanMapper;
import com.wuzheng.wisgo.sanitation.cloud.service.plan.*;
import com.wuzheng.wisgo.sanitation.framework.base.service.impl.BaseServiceImpl;
import com.wuzheng.wisgo.sanitation.framework.core.constant.SysRespEnum;
import com.wuzheng.wisgo.sanitation.framework.core.util.ServiceAssert;
import com.wuzheng.wisgo.sanitation.framework.util.StringUtils;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.util.Date;
import java.util.List;

/**
 * @author：hoipang
 * @date：Created in 2019-12-18
 * @description：道路作业计划服务实现类
 * @modified By：
 * @version: 1.0
 */
@Service
public class JobPlanServiceImpl extends BaseServiceImpl<JobPlan> implements JobPlanService {
    @Resource
    JobPlanRoadService jobPlanRoadService;
    @Resource
    JobPlanTransferService jobPlanTransferService;
    @Resource
    JobPlanShiftService jobPlanShiftService;
    @Resource
    JobPlanVehicleService jobPlanVehicleService;

    @Override
    public List<JobPlanDTO> listJobPlanDTOs(JobPlanListParam jobPlanListParam) {
        JobPlanMapper jobPlanMapper = this.getMapper(JobPlanMapper.class);
        List<JobPlanDTO> list;
        if (jobPlanListParam.getPageSize() != null && jobPlanListParam.getPageIndex() != null) {
            Page<JobPlanDTO> page = new Page<>(jobPlanListParam.getPageIndex(), jobPlanListParam.getPageSize());
            list = jobPlanMapper.pageJobPlanDTOs(page, jobPlanListParam.getPlanName(), jobPlanListParam.getJobType());
            return list;
        }
        list = jobPlanMapper.listJobPlanDTOs(jobPlanListParam.getPlanName(), jobPlanListParam.getJobType());
        return list;
    }

    @Override
    public List<JobPlanDetailRouteDTO> listDetailRouteDTOs(String jobTypeCode) {
        JobPlanMapper jobPlanMapper = this.getMapper(JobPlanMapper.class);

        List<JobPlanDetailRouteDTO> routeDTOList = jobPlanMapper.listRoutes(jobTypeCode);

        return routeDTOList;
    }

    @Override
    public void removeJobPlans(List<String> list) {
        ServiceAssert.isTrue(list != null && !list.isEmpty(), SysRespEnum.ILLEGAL_ARGUMENT.getCode(),
                ErrorConst.Common.ARGUMENT_NOT_NULL);
        //删除plan主表，删除plan所有附表
        Wrapper<JobPlan> planWrapper = new EntityWrapper<>();
        planWrapper.in("id", list);
        List<JobPlan> jobPlanList = this.selectList(planWrapper);
        jobPlanList.forEach(c -> {
            Wrapper<JobPlanShift> shiftWrapper = new EntityWrapper<>();
            shiftWrapper.eq("plan_id", c.getId());
            List<JobPlanShift> shiftList = jobPlanShiftService.selectList(shiftWrapper);
            shiftList.forEach(shift -> {
                shift.setDeFlag(true);
                jobPlanShiftService.update(shift, shiftWrapper);
            });

            Wrapper<JobPlanVehicle> vehicleWrapper = new EntityWrapper<>();
            vehicleWrapper.eq("plan_id", c.getId());
            List<JobPlanVehicle> vehicleList = jobPlanVehicleService.selectList(vehicleWrapper);
            for (JobPlanVehicle vehicle : vehicleList) {
                vehicle.setDeFlag(true);
                jobPlanVehicleService.update(vehicle, vehicleWrapper);
            }

            switch (c.getJobTypeId()) {
                case Constants.JobType.TRANSFER:
                    Wrapper<JobPlanTransfer> transferWrapper = new EntityWrapper<>();
                    transferWrapper.eq("plan_id", c.getId());
                    List<JobPlanTransfer> transfers = jobPlanTransferService.selectList(transferWrapper);
                    transfers.forEach(item -> {
                        item.setDeFlag(true);
                        jobPlanTransferService.update(item, transferWrapper);
                    });
                    break;
                default:
                    Wrapper<JobPlanRoad> roadWrapper = new EntityWrapper<>();
                    roadWrapper.eq("plan_id", c.getId());
                    List<JobPlanRoad> planRoads = jobPlanRoadService.selectList(roadWrapper);
                    planRoads.forEach(road -> {
                        road.setDeFlag(true);
                        jobPlanRoadService.update(road, roadWrapper);
                    });
                    break;
            }
        });

        this.updateBatchById(jobPlanList, jobPlanList.size());
    }

    @Override
    public JobPlanDetailDTO selectJobPlanDetailDTO(JobPlanDetailParam jobPlanDetailParam) {
        JobPlanMapper jobPlanMapper = this.getMapper(JobPlanMapper.class);
        JobPlanDetailDTO jobPlanDetailDTO = jobPlanMapper.selectJobPlanDetailDTO(jobPlanDetailParam.getId(),
                jobPlanDetailParam.getJobTypeCode());
        ServiceAssert.isTrue(jobPlanDetailDTO != null, SysRespEnum.SUCCESS.getCode(), ErrorConst.Common.QUERY_RESULT_NOT_EXIST);
        return jobPlanDetailDTO;
    }

    @Override
    public String insertOrUpdate(User user, JobPlanSaveParam jobPlanSaveParam) {
        JobPlan jobPlan = new JobPlan();
        jobPlan.setCustomerId(user.getCustomerId());
        jobPlan.setJobName(jobPlanSaveParam.getPlanName());
        jobPlan.setJobTypeId(jobPlanSaveParam.getJobTypeCode());
        jobPlan.setJobType(jobPlanSaveParam.getJobTypeName());
        jobPlan.setJobFrequencyId(jobPlanSaveParam.getJobFrequencyCode());
        jobPlan.setJobFrequency(jobPlanSaveParam.getJobFrequencyName());
        jobPlan.setRemark(jobPlanSaveParam.getRemark());

        String method = jobPlanSaveParam.getMethod();
        Boolean update = method.equals(InfixDataEnum.UPDATE.getTypeId()) && StringUtils.isNotBlank(jobPlanSaveParam.getId());

        Boolean flag = update || method.equals(InfixDataEnum.ADD.getTypeId());
        ServiceAssert.isTrue(flag, SysRespEnum.ILLEGAL_ARGUMENT.getCode(), SysRespEnum.ILLEGAL_ARGUMENT.getMessage());

        if (method.equals(InfixDataEnum.ADD.getTypeId())) {
            jobPlan.setDeFlag(false);
            jobPlan.setCreator(user.getName());
            jobPlan.setCreateTime(new Date());
            this.insert(jobPlan);
        }

        String planId = StringUtils.isBlank(jobPlanSaveParam.getId()) ? jobPlan.getId() : jobPlanSaveParam.getId();

        if (method.equals(InfixDataEnum.UPDATE.getTypeId())) {
            jobPlan.setId(planId);
            jobPlan.setModifier(user.getName());
            jobPlan.setModifyTime(new Date());
            this.updateById(jobPlan);

            switch (jobPlanSaveParam.getJobTypeCode()) {
                case Constants.JobType.TRANSFER:
                    EntityWrapper<JobPlanTransfer> transferWrapper = new EntityWrapper<>();
                    transferWrapper.eq("plan_id", planId);
                    jobPlanTransferService.delete(transferWrapper);
                    break;
                default:
                    EntityWrapper<JobPlanRoad> roadWrapper = new EntityWrapper<>();
                    roadWrapper.eq("plan_id", planId);
                    jobPlanRoadService.delete(roadWrapper);
                    break;
            }

            EntityWrapper<JobPlanVehicle> vehicleWrapper = new EntityWrapper<>();
            vehicleWrapper.eq("plan_id", planId);
            jobPlanVehicleService.delete(vehicleWrapper);

            EntityWrapper<JobPlanShift> shiftWrapper = new EntityWrapper<>();
            shiftWrapper.eq("plan_id", planId);
            jobPlanShiftService.delete(shiftWrapper);
        }
        switch (jobPlanSaveParam.getJobTypeCode()) {
            case Constants.JobType.TRANSFER:
                jobPlanSaveParam.getRoadParams().forEach(m -> {
                    JobPlanTransfer transfer = new JobPlanTransfer();
                    transfer.setPlanId(planId);
                    transfer.setRouteId(m.getId());
                    transfer.setRoadName(m.getRoadName());
                    transfer.setTrashLong(Double.valueOf(m.getLongitude()));
                    transfer.setTrashLat(Double.valueOf(m.getLatitude()));
                    transfer.setErrorThreshold(Double.valueOf(m.getThreshold()));
                    transfer.setTrashId(m.getTrashId());
                    transfer.setDeFlag(false);
                    transfer.setCreator(user.getName());
                    transfer.setCreateTime(new Date());
                    jobPlanTransferService.insert(transfer);
                });
                break;
            default:
                jobPlanSaveParam.getRoadParams().forEach(m -> {
                    JobPlanRoad road = new JobPlanRoad();
                    road.setPlanId(planId);
                    road.setRoadId(m.getId());
                    road.setRoadName(m.getRoadName());
                    road.setDeFlag(false);
                    road.setCreator(user.getName());
                    road.setCreateTime(new Date());
                    jobPlanRoadService.insert(road);
                });
                break;
        }
        jobPlanSaveParam.getVehicleParams().forEach(m -> {
            JobPlanVehicle vehicle = new JobPlanVehicle();
            vehicle.setPlanId(planId);
            vehicle.setVehCode(m.getVehCode());
            vehicle.setVehVinCode(m.getVehVinCode());
            vehicle.setVehUseSortId(m.getVehUseSortId());
            vehicle.setVehUseSortName(m.getVehUseSortName());
            vehicle.setDeFlag(false);
            vehicle.setCreator(user.getName());
            vehicle.setCreateTime(new Date());
            jobPlanVehicleService.insert(vehicle);
        });

        jobPlanSaveParam.getShiftParams().forEach(m -> {
            JobPlanShift jobPlanShift = new JobPlanShift();
            jobPlanShift.setPlanId(planId);
            jobPlanShift.setShiftId(m.getId());
            jobPlanShift.setShiftName(m.getShiftName());
            jobPlanShift.setStartWorkTime(m.getStartWorkTime());
            jobPlanShift.setOffWorkTime(m.getOffWorkTime());
            jobPlanShift.setDeFlag(false);
            jobPlanShift.setCreator(user.getName());
            jobPlanShift.setCreateTime(new Date());
            jobPlanShiftService.insert(jobPlanShift);
        });

        return planId;
    }
}
